#pragma once
#ifndef CLIB_STACK_H
#define CLIB_STACK_H

#include "clib_type.h"
#include "clib_queue.h"
#include "clib_stack_netif.h"
#include "clib_sock.h"

#define  CLIB_CTX_NUM       64

#ifdef __cplusplus
extern "C" {
#endif

typedef enum send_type_e 
{
    send_data_flag,
    send_data_all
} send_type_t;

extern clib_stack_t l4_satck;

typedef struct clib_stack_ctx_s
{
    /** TODO 思考相关关系 **/
    clib_queue_t    wait_list;          /*** wait 链表 ***/
    clib_queue_t    timeout_list;       /*** 超时链表 ***/
    clib_queue_t    free_list;          /*** 空闲链表 ***/
    clib_queue_t    conn_list;          /*** 发起新连接链表 ***/
    clib_queue_t    ack_list;           /*** ACK  确认链表 ***/
    clib_queue_t    send_list;          /*** DATA 发送链表 ***/
    clib_queue_t    rset_list;          /*** RSET 发送链表 ***/
    clib_queue_t    close_list;         /*** close关闭链表 ***/
    clib_queue_t    acpt_list;          /*** acpt 接收链表 ***/
    clib_queue_t    rto_list;           /*** rto  超时链表 ***/
    clib_queue_t    wack_list;          /*** wack 操作链表 ***/

    stack_netif_t  *netif[CLIB_CTX_NUM];

    void           *sock_table;
    void           *hash_table;
    void           *listen_table;

    i32_t           ctx_idx;

    i32_t           socket_id;
    i32_t           sock_n;
    i32_t           wait_n;
    i32_t           waitout_n;
    i32_t           free_n;
    i32_t           conn_n;
    i32_t           ack_n;
    i32_t           send_n;
    i32_t           rset_n;
    i32_t           close_n;
    i32_t           acpt_n;
    i32_t           ifnet_n;
    i32_t           core_id;
    i32_t           time_out;
    i32_t           rto_n;
    i32_t           wack_n;
    i32_t           wack;       /** 延时ack  **/
    i32_t           sack;       /** sack支持 **/
} stack_ctx_t;

typedef struct clib_stack_s
{
   i32_t           sock_n;
   i32_t           ctx_n;
   i32_t           ifnet;
   stack_ctx_t ctx[CLIB_CTX_NUM];
   void           *sock_table;
} clib_stack_t;

void  
clib_stack_index_set(i32_t idx);

i32_t 
clib_stack_index_get();

clib_stack_t* 
clib_stack_create(i32_t sock_n, i32_t ctx_n, i32_t ifnet_n, i32_t socket_id);

void
clib_stack_ctx_init(stack_ctx_t* ctx);

void
clib_stack_free(clib_stack_t* stack);

stack_ctx_t* 
clib_get_stack_ctx(clib_stack_t* stack, i32_t queue);

clib_sock_t* 
clib_get_sock_new_by_stack(stack_ctx_t* ctx);

clib_sock_t*
clib_get_sock_by_id(clib_stack_t* ctx,i32_t sfd);

void
clib_put_sock_to_stack(stack_ctx_t* ctx, clib_sock_t* sock);

i32_t
clib_stack_set_netif(clib_stack_t* stack,stack_netif_t  *netif,i32_t ifnet);

#ifdef __cplusplus
}
#endif

#endif